home *** CD-ROM | disk | FTP | other *** search
/ PC World Komputer 2010 April / PCWorld0410.iso / pluginy Firefox / 5817 / 5817.xpi / chrome / content / treeDataTable.js < prev    next >
Text File  |  2010-02-11  |  12KB  |  336 lines

  1. // ****** table event handling and display ******
  2. function TreeDataTable(sTreeId) {
  3.   this.mTreeId = sTreeId;
  4.   this.treeTable = null; // Tree containing listing of current table
  5. }
  6.  
  7. TreeDataTable.prototype = {
  8.   // Last row/col that was clicked on (may be inaccurate if scrolling happened)
  9.   lastRow: -1,
  10.   lastCol: null,
  11.  
  12.   // Initialize: Set up the treeview which will display the table contents
  13.   init: function() {        
  14.     this.treeTable = document.getElementById(this.mTreeId);
  15.   },
  16.  
  17.   // ShowTable: Show/hide any currently displayed table data
  18.   ShowTable: function(bShow) {
  19.     if (this.treeTable == null) 
  20.       return;
  21.  
  22.     this.treeTable.childNodes[0].hidden = !bShow;
  23.     this.treeTable.childNodes[1].hidden = !bShow;
  24.  
  25.     if (!bShow) {
  26.       // remove all of the child rows/columns
  27.       SmGlobals.$empty(this.treeTable.childNodes[0]);
  28.       SmGlobals.$empty(this.treeTable.childNodes[1]);
  29.     } 
  30.   },
  31.  
  32.   // UserCopyCell: copy the cell contents
  33.   UserCopyCell: function() {
  34.     //Issue #392: lastRow = -1, if a row is not clicked over; 0 means first row.
  35.     if (this.lastRow != -1  && this.lastCol) {
  36.       var sCell= this.treeTable.view.getCellText(this.lastRow, this.lastCol);
  37.       if (sCell)
  38.         SQLiteManager.copyText(sCell);
  39.     }
  40.   },
  41.   
  42.   // UserCopyRows: copy all currently highlighted rows
  43.   // sFormat: csv, csv-excel, sql
  44.   UserCopyRows: function(sFormat) {
  45.     var sel = this.treeTable.view.selection;
  46.     var start = new Object();
  47.     var end = new Object();
  48.     var iRangeCount = sel.getRangeCount();
  49.     var aOut = [];
  50.     for (var iRange = 0; iRange < iRangeCount; iRange++) {
  51.       sel.getRangeAt(iRange,start,end);
  52.       for (var iRow = start.value; iRow <= end.value; iRow++) {
  53.         aOut.push(this.GetRowData(iRow, sFormat));
  54.       }
  55.     }
  56.     if (aOut.length > 0)
  57.       SQLiteManager.copyText(aOut.join("\n"));
  58.   },
  59.  
  60.   // GetRowData: Get the contents of an entire numbered row, using the specified format
  61.   GetRowData: function(iRow, sFormat) {
  62.     var result = [], oCol, txt;
  63.     var sExtraColId = "";
  64.     var allCols = this.treeTable.getElementsByTagName("treecol");
  65.     for (var i = 0; i < allCols.length; i++) {
  66.       if (allCols.item(i).hasAttribute("extraRowId"))
  67.         sExtraColId = allCols.item(i).id;
  68.     }
  69.  
  70.     for (var i = 0; i < this.treeTable.columns.length; i++) {
  71.       oCol = this.treeTable.columns.getColumnAt(i);
  72.       if (sExtraColId == oCol.id) {//Issue #151
  73.         continue;
  74.       }
  75.  
  76.       txt = this.treeTable.view.getCellText(iRow, oCol);
  77.       if (txt == null) {
  78.         if (sFormat == "csv")
  79.           txt = '';
  80.         if (sFormat == "sql")
  81.           txt = 'null';
  82.       }
  83.       else {
  84.         if (typeof txt == "string")
  85.           txt = txt.replace("\"", "\"\"", "g");
  86.         txt = '"' + txt + '"';
  87.       }
  88.       result.push(txt);
  89.     }
  90.  
  91.     if (sFormat == "csv") {
  92.       var sPrefVal = sm_prefsBranch.getCharPref("jsonEximSettings");
  93.       var obj = JSON.parse(sPrefVal);
  94.  
  95.       var cSeparator = obj.csv.export.separator;
  96.       //var cEncloser = obj.csv.export.encloser;
  97.       //var bColNames = obj.csv.export.includeColNames;
  98.  
  99.       return result.join(cSeparator);
  100.     }
  101.     if (sFormat == "csv-excel")
  102.       return result.join('\t');
  103.     if (sFormat == "sql") //do we need column names too?
  104.       return "INSERT INTO \"someTable\" VALUES (" + result.toString() + ");";
  105.  
  106.     return "";
  107.   },
  108.  
  109.   // UserTreeClick: Handle the user clicking on the tree
  110.   UserTreeClick: function(ev) {
  111.   // This event happens AFTER the window has scrolled (if necessary). This means that if the user clicked on an element that is partially off screen, and the screen scrolls to fully display it, then the mouse may no longer be over the correct element.
  112.   //if (ev.button == 2) // Right-click
  113.   //store the row/column that the click occurred on; used when copying cell text
  114.     if (ev && this.treeTable && ev.type == "click") {
  115.       var row = {}, col = {}, obj = {};
  116.       this.treeTable.treeBoxObject.getCellAt(ev.clientX, ev.clientY, row, col, obj);
  117.       //Issue #392: if the click is not over a row, row.value = -1
  118.       if (row && row.value != -1 && col && col.value) {
  119. //alert(row.value + "=" + obj.value);
  120.         // clicked on a cell
  121.         this.lastRow = row.value;
  122.         this.lastCol = col.value;
  123.       }
  124.       else {
  125.         this.lastRow = null;
  126.         this.lastCol = null;
  127.       }
  128.     }
  129.   },
  130.  
  131.   AddTreecol: function(treecols, sId, col, sColType, iWidth, bLast, bExtraRowId, sClickFn, sBgColor) {
  132.     //bExtraRowId = true for rowid column which is not one of the tables'columns
  133.     var treecol = document.createElement("treecol");
  134.     treecol.setAttribute("label", col);
  135.     treecol.setAttribute("sDataType", sColType);
  136. //    treecol.setAttribute("smSortDir", "none");
  137.     if (bExtraRowId)
  138.       treecol.setAttribute("extraRowId", true);
  139.     treecol.setAttribute("id", sId);
  140.     treecol.setAttribute("width", iWidth);
  141.     treecol.setAttribute("minwidth", 60);
  142.     //Issue #378
  143.     //treecol.setAttribute("context", 'mp-data-treecol');
  144.     if (sClickFn != null)
  145.       treecol.setAttribute("onclick", sClickFn);
  146.     if (sBgColor != null)
  147.       treecol.setAttribute("style", "color:"+sBgColor);
  148.  
  149. // sColType is based on data in first row, which may not be the same
  150. // as the type defined for that column in schema
  151. //    if (sColType != null)
  152. //      treecol.setAttribute("tooltiptext", col + " (" + sColType + ")");
  153.  
  154.     if (bLast) {
  155.       //want to do anything special for the last column? do it here.
  156.       treecol.setAttribute("flex", 1);
  157.     }
  158.     treecols.appendChild(treecol);
  159.  
  160.     //add a splitter after every column
  161.     var splitter = document.createElement("splitter");
  162.     splitter.setAttribute("class", "tree-splitter");        
  163.     splitter.setAttribute("resizebefore", "closest");
  164.     splitter.setAttribute("resizeafter", "grow");
  165.     splitter.setAttribute("oncommand", "SQLiteManager.saveBrowseTreeColState(this)");
  166.     treecols.appendChild(splitter); 
  167.   },
  168.  
  169.   // iExtraColForRowId: indicates column number for the column which is a rowid
  170.   //  0 means no extra rowid, column numbering begins with 1
  171.   //  use this while copying Issue #151
  172.   createColumns: function(aColumns, iExtraColForRowId, aSortInfo, sClickFn) {
  173.     var treecols = this.treeTable.firstChild;
  174.     SmGlobals.$empty(treecols);
  175.  
  176.     var iColumnCount = 0;
  177.     var iRow;
  178.     var iWidth, iTotalWidth, iMaxWidth;
  179.     var sColType;
  180.     var allCols = [];
  181.     for (var col in aColumns) {
  182.       iColumnCount = iColumnCount + 1;
  183.       var aTemp = [aColumns[col][0], aColumns[col][1]];
  184.       allCols.push(aTemp);
  185.     }
  186.  
  187.     var iTreeWidth = this.treeTable.boxObject.width;
  188.     for (var iColumn = 0; iColumn < iColumnCount; iColumn++) {
  189.       iTotalWidth = 0;
  190.       iMaxWidth = 0;
  191.       iTotalWidth = iTreeWidth/iColumnCount;
  192.       if (iTotalWidth < 60) iTotalWidth = 60;
  193.  
  194.       sColType = '';
  195.  
  196.       var sBgColor = null;
  197.       for(var i = 0; i < aSortInfo.length; i++) {
  198.         if (aSortInfo[i][0] == allCols[iColumn][0]) {
  199.           switch (aSortInfo[i][1]) {
  200.             case "asc":
  201.               sBgColor = "green";
  202.               break;
  203.             case "desc":
  204.               sBgColor = "red";
  205.               break;
  206.           }
  207.         }
  208.       }
  209.  
  210.       var bExtraColForRowId = (iColumn==iExtraColForRowId-1) ? true : false;
  211.       this.AddTreecol(treecols, iColumn, allCols[iColumn][0], sColType, iTotalWidth, (iColumn==iColumnCount-1?true:false), bExtraColForRowId, sClickFn, sBgColor);
  212.     }
  213.   },
  214.  
  215.   adjustColumns: function(objColInfo) {
  216.     if (typeof objColInfo.arrId == "undefined" || typeof objColInfo.arrWidth == "undefined")
  217.       return;
  218.     var aCols = this.treeTable.querySelectorAll("treecol");
  219.     for (var i = 0; i < aCols.length; i++) {
  220.       var pos = objColInfo.arrId.indexOf(aCols.item(i).id);
  221.       if (pos >= 0)
  222.         aCols.item(i).width = objColInfo.arrWidth[pos];
  223.     }
  224.   },
  225.  
  226.   // PopulateTableData: Assign our custom treeview
  227.   PopulateTableData: function(aTableData, aColumns, aTypes) {   
  228.     this.treeTable.view = new this.DatabaseTreeView(aTableData, aColumns, aTypes);
  229.     this.ShowTable(true);
  230.   },
  231.  
  232.   // DatabaseTreeView: Create a custom nsITreeView
  233.   DatabaseTreeView: function(aTableData, aColumns, aTypes) {
  234.     // http://kb.mozillazine.org/Sorting_Trees
  235.     // 2 dimensional array containing table contents
  236.     this.aTableData = aTableData;
  237.     // Column information
  238.     this.aColumns = aColumns;
  239.     this.aTypes = aTypes;
  240.  
  241.     this.aOrder = [];
  242.     for (var i=0; i < this.aColumns.length; i++)
  243.      this.aOrder.push(-1);//0=asc; 1=desc
  244.  
  245.     // Number of rows in the table
  246.     this.rowCount = aTableData.length;
  247.  
  248.     this.getCellText = function(row,col) {
  249.       var sResult;
  250.       try { sResult= this.aTableData[row][col.id]; }
  251.       catch (e) { return "<" + row + "," + col.id + ">"; }
  252.       return sResult;
  253.     };
  254.  
  255.     this.setTree             = function(treebox){ this.treebox=treebox; };
  256.     this.isContainer         = function(row){ return false; };
  257.     this.isSeparator         = function(row){ return false; };
  258.     this.isSorted            = function(row){ return false; };
  259.     this.cycleHeader         = function(col){ this.SortColumn(col); }
  260.     this.getLevel            = function(row){ return 0; };
  261.     this.getImageSrc         = function(row,col){ return null; };
  262.     this.getRowProperties    = function(row,properties){};
  263.     this.getCellProperties   = function(row,col,properties) {
  264.       var atomService = Components.classes["@mozilla.org/atom-service;1"].getService(Components.interfaces.nsIAtomService);
  265.       switch(this.aTypes[row][col.id]) {
  266.         case SQLiteTypes.INTEGER:
  267.           var atom = atomService.getAtom("integervalue");
  268.           properties.AppendElement(atom);
  269.           break;
  270.         case SQLiteTypes.FLOAT:
  271.           var atom = atomService.getAtom("floatvalue");
  272.           properties.AppendElement(atom);
  273.           break;
  274.         case SQLiteTypes.BLOB:
  275.           var atom = atomService.getAtom("blobvalue");
  276.           properties.AppendElement(atom);
  277.           break;
  278.         case SQLiteTypes.NULL: 
  279.           var atom = atomService.getAtom("nullvalue");
  280.           properties.AppendElement(atom);
  281.           break;
  282.         case SQLiteTypes.TEXT:
  283.         default:
  284.           var atom = atomService.getAtom("textvalue");
  285.           properties.AppendElement(atom);
  286.           break;
  287.       }
  288.       if (typeof this.getCellText(row,col) == "number") {
  289.         var atom = atomService.getAtom("numbervalue");
  290.         properties.AppendElement(atom);
  291.       }
  292.       var atom = atomService.getAtom("tabledata");
  293.       properties.AppendElement(atom);
  294.     };
  295.     this.getColumnProperties = function(colid,col,properties){};
  296.  
  297.     this.SortColumn = function(col) {
  298.       var index  = col.id; 
  299.       var name = this.aColumns[index][0];
  300.       var type = this.aColumns[index][1];
  301.       var isnum = ((this.aColumns[index][2]==1)?1:0);
  302.       this.aOrder[index] = (this.aOrder[index]==0)?1:0;
  303.       var order = this.aOrder[index];
  304. //alert(order+"="+name);
  305.       
  306.       this.SortTable(this.aTableData,index,order,isnum);  // sort the table
  307.       this.rowCount= this.aTableData.length; // Not the right place for this but...
  308.       this.treeTable.view = new treeView(this.aTableData, this.aColumns, this.rowCount);       
  309.     };
  310.  
  311.   // This is the actual sorting method, extending the array.sort() method
  312.     this.SortTable = function(table,col,order,isnum) {
  313.       if(isnum){ // use numeric comparison 
  314.           if(order==0){ // ascending 
  315.               this.columnSort= function (a,b){ return (a[col]-b[col]); };
  316.           }
  317.           else{ // descending 
  318.               this.columnSort= function (a,b){ return (b[col]-a[col]); };
  319.           }
  320.       }
  321.       else{ // use string comparison 
  322.           if(order==0){ // ascending 
  323.               this.columnSort= function(a,b){
  324.                   return (a[col]<b[col])?-1:(a[col]>b[col])?1:0; };
  325.           }
  326.           else{ // descending 
  327.               this.columnSort= function(a,b){
  328.                   return (a[col]>b[col])?-1:(a[col]<b[col])?1:0; };
  329.           }
  330.       }
  331.       // use array.sort(comparer) method
  332.       table.sort(this.columnSort);
  333.     };
  334.   }
  335. };
  336.